package com.itheima.d2_collection_traverse;
import java.util.ArrayList;
import java.util.Collection;
import java.util.function.Consumer;

/**
 * 1、集合中存储的是元素的什么信息?
 * 集合中存储的是元素对象的地址。
     目标：Collection集合的遍历方式三：JDK8开始新增的Lambda表达式。
 Lambda表达式遍历集合:
 得益于JDK 8开始的新技术Lambda表达式，提供了一种更简单、更直接的方式来遍历集合。

 default void forEach(Consumer<? super T> action)       结合lambda遍历集合

 Collection<String> lists = new ArrayList<>();
 ...
 lists.forEach(new Consumer<String>() {
@Override
public void accept(String s) {
System.out.println(s);
}
});
简化：
 lists.forEach(s -> {
 System.out.println(s);
 });
 //  lists.forEach(s -> System.out.println(s));


 */
public class CollectionDemo03 {
    public static void main(String[] args) {
        Collection<String> c = new ArrayList<>();
        c.add("赵敏");
        c.add("小昭");
        c.add("殷素素");
        c.add("周芷若");
        System.out.println(c);
        // [赵敏, 小昭, 殷素素, 周芷若]
        //                     s

        // default void forEach(Consumer<? super T> action):  结合Lambda表达式遍历集合：

        //Consumer是一个接口不能创建对象，所以用匿名内部类,forEach的源码：
        /*
          default void forEach(Consumer<? super T> action) {
        Objects.requireNonNull(action);
        for (T t : this) {
            action.accept(t);
        }
    }
        分析：new的匿名内部类会给到action参数，然后先判断是否为空，this代表主调，也就是c集合
             然后用增强for遍历c集合，每次遍历c集合得到的数据，
             都会用action（代表着consumer接口new的匿名内部类对象）调用匿名内部类中重写的accept方法，
             并且把从c集合遍历到的数据传给accept方法
             并且consumer接口是@FunctionalInterface的函数式接口，可以用lambda简化
         */
        c.forEach(new Consumer<String>() {
            @Override
            public void accept(String s) {
                System.out.println(s);
            }
        });

        c.forEach((String s) -> {
                System.out.println(s);
        });

        c.forEach(s  -> {
            System.out.println(s);
        });

        c.forEach(s  -> System.out.println(s) );


        /*
        1.是否函数式接口，2.前后调用参数是否唯一，3.方法内部行数为一行，
        4.内部是否使用了函数调用，根据这四步一步步化是可以的
        out是一个对象，println是一个方法，所以能进行实例方法引用
         */
        c.forEach(System.out::println );

        System.out.println("----------自己写一遍，先增强for小试牛刀-------");

        Collection<String> a1 = new ArrayList<>();
        a1.add("曾季洪");
        a1.add("牛逼");
        a1.add("我最牛逼");
        a1.add("啦啦啦啦啦啦");
        for (String s : a1) {
            System.out.println(s);
        }

        System.out.println("-------foreach遍历------");
        //default void forEach(Consumer<? super T> action)       结合lambda遍历集合
        a1.forEach(new Consumer<String>() {
            @Override
            public void accept(String s) {
                System.out.println(s);
            }
        });

        System.out.println("---------lambda简化-------");
        a1.forEach((String s)->{
            System.out.println(s);
        });

        System.out.println("---------lambda再简化-------");
        a1.forEach(s -> {
            System.out.println(s);
        });

        a1.forEach(s -> System.out.println(s));
        System.out.println("-------------");
        a1.forEach(System.out::println);

    }
}










